package com.zhang.study.chapter10;

/**
 * 将链表根据某个值分成三个部分
 * 1. 小于区
 * 2. 等于区
 * 3. 大于区
 * 最后返回头结点
 */
public class Code03_SmallerEqualBigger {

    public static class Node {
        public int value;
        public Node next;

        public Node(int data) {
            this.value = data;
        }
    }

    public static Node partition1(Node head, int pivot) {
        int size = 0;
        Node cur = head;
        while (cur != null) {
            size++;
            cur = cur.next;
        }
        Node[] nodes = new Node[size];
        cur = head;
        size = 0;
        while (cur != null) {
            nodes[size++] = cur;
            cur = cur.next;
        }
        arrPartition(nodes, pivot);
        for (int i = 1; i < nodes.length; i++) {
            nodes[i - 1].next = nodes[i];
        }
        nodes[size - 1].next = null;
        return nodes[0];
    }

    private static void arrPartition(Node[] nodes, int pivot) {
        int l = -1;
        int r = nodes.length;
        int i = 0;
        while (i != r) {
            if (nodes[i].value < pivot) {
                swap(++l, i++, nodes);
            } else if (nodes[i].value == pivot) {
                i++;
            } else {
                swap(i, --r, nodes);
            }
        }
    }

    private static void swap(int i, int j, Node[] nodes) {
        Node temp = nodes[i];
        nodes[i] = nodes[j];
        nodes[j] = temp;
    }

    public static Node partition2(Node head, int pivot) {
        Node smallHead = null;
        Node smallCur = null;
        Node equalHead = null;
        Node equalCur = null;
        Node bigHead = null;
        Node bigCur = null;
        Node cur;

        while (head != null) {
            cur = head.next;
            head.next = null;
            if (head.value < pivot) {
                if (smallHead == null) {
                    smallHead = head;
                    smallCur = head;
                } else {
                    smallCur.next = head;
                    smallCur = smallCur.next;
                }
            } else if (head.value == pivot) {
                if (equalHead == null) {
                    equalHead = head;
                    equalCur = head;
                } else {
                    equalCur.next = head;
                    equalCur = equalCur.next;
                }
            } else {
                if (bigHead == null) {
                    bigHead = head;
                    bigCur = head;
                } else {
                    bigCur.next = head;
                    bigCur = bigCur.next;
                }
            }
            head = cur;
        }
        // 拼接三个链表
        if (smallCur != null) { // 倘若小于区域存在
            smallCur.next = equalHead;
            equalCur = equalCur != null ? equalCur : smallCur;
        }
        if(equalCur != null){
            equalCur.next = bigHead;
        }
        return smallHead != null ? smallHead : equalHead != null ? equalHead : bigHead;
    }

    public static void printLinkedList(Node node) {
        System.out.print("Linked List: ");
        while (node != null) {
            System.out.print(node.value + " ");
            node = node.next;
        }
        System.out.println();
    }
    public static void main(String[] args) {
        Node head1 = new Node(7);
        head1.next = new Node(9);
        head1.next.next = new Node(1);
        head1.next.next.next = new Node(8);
        head1.next.next.next.next = new Node(5);
        head1.next.next.next.next.next = new Node(2);
        head1.next.next.next.next.next.next = new Node(5);
        printLinkedList(head1);
//        head1 = partition1(head1,4);
//        printLinkedList(head1);
        head1 = partition2(head1,5);
        printLinkedList(head1);

    }

}
